class Github
  attr_reader :username, :password, :apiurl
  attr_accessor :events, :gists, :gitdata, :issues, :orgs, :pullreqs, :repos, :users

  def initialize(username, password)
    @apiurl = 'https://api.github.com'
    @username = username
    @password = password
    @events = Events.new(self)
    @gists = Gists.new(self)
    @gitdata = GitData.new(self)
    @issues = Issues.new(self)
    @orgs = Orgs.new(self)
    @pullreqs = PullReq.new(self)
    @repos = Repos.new(self)
    @users = Users.new(self)
    @events = Events.new(self)
  end

  def head(path)
    uri = URI(buildurl(path))
    req = Net::HTTP::Head.new(uri.request_uri)
    req.basic_auth @username, @password
    res = Net::HTTP.start(uri.hostname, use_ssl: true, verify_mode: OpenSSL::SSL::VERIFY_NONE) { |http|
      http.request(req)
    }
    JSON.parse(res.body)
  end

  def get(path)
    uri = URI(buildurl(path))
    req = Net::HTTP::Get.new(uri.request_uri)
    req.basic_auth @username, @password
    res = Net::HTTP.start(uri.hostname, use_ssl: true, verify_mode: OpenSSL::SSL::VERIFY_NONE) { |http|
      http.request(req)
    }
    JSON.parse(res.body)
  end

  def post(path, data=nil)
    uri = URI(buildurl(path))
    req = Net::HTTP::Post.new(uri.request_uri, initheader = {'Content-Type' => 'application/json'})
    req.basic_auth @username, @password
    req.body = data
    res = Net::HTTP.start(uri.hostname, use_ssl: true, verify_mode: OpenSSL::SSL::VERIFY_NONE) { |http|
      http.request(req)
    }
    res.body
  end

  def patch(path, data)
    uri = URI(buildurl(path))
    req = Net::HTTP::Patch.new(uri.request_uri, initheader = {'Content-Type' => 'application/json'})
    req.basic_auth @username, @password
    req.body = data
    res = Net::HTTP.start(uri.hostname, use_ssl: true, verify_mode: OpenSSL::SSL::VERIFY_NONE) { |http|
      http.request(req)
    }
    JSON.parse(res.body)
  end

  def put(path, data=nil)
    uri = URI(buildurl(path))
    req = Net::HTTP::Put.new(uri.request_uri, initheader = {'Content-Type' => 'application/json'})
    req.basic_auth @username, @password
    req.body = data
    res = Net::HTTP.start(uri.hostname, use_ssl: true, verify_mode: OpenSSL::SSL::VERIFY_NONE) { |http|
      http.request(req)
    }
    JSON.parse(res.body)
  end

  def delete(path, data=nil)
    uri = URI(buildurl(path))
    req = Net::HTTP::Delete.new(uri.request_uri)
    req.basic_auth @username, @password
    req.body = data
    res = Net::HTTP.start(uri.hostname, use_ssl: true, verify_mode: OpenSSL::SSL::VERIFY_NONE) { |http|
      http.request(req)
    }
    res.body ? JSON.parse(res.body) : res.code
  end

  def buildurl(path)
    @apiurl + ((path[0] == '/') ? path : ('/%s' % path))
  end

  def parameterize(params)
    URI.escape(params.collect { |k, v| "#{k}=#{v}" }.join('&'))
  end

  def removeEmptyParams(params)
    params.delete_if { |k, v| v.nil? }
  end
end